package com.example.rabcdemo.interceptor;

import cn.hutool.json.JSONUtil;
import cn.hutool.jwt.JWT;
import com.example.rabcdemo.annotation.RequestPermission;
import com.example.rabcdemo.common.Result;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.stereotype.Component;
import org.springframework.web.method.HandlerMethod;
import org.springframework.web.servlet.HandlerInterceptor;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.util.List;

/*
先完成再完美->思维连贯性，充足的时间
先完美再完成->时间不够，思维断裂，过度优化过早优化
 */
@Component
@Slf4j
public class PermissionInterceptor implements HandlerInterceptor {
    @Autowired
    private RedisTemplate redisTemplate;
    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) {
        //handler->向下转型
        if(handler instanceof HandlerMethod){
            //login直接放行
            String requestURI = request.getRequestURI();
            log.info(requestURI);
            if(requestURI.contains("login")){
                return true;
            }

            //token->请求头request
            String token = request.getHeader("Authorization");
            log.info("拿到的token：{}",token);
            //token-> id,roleId
            String id = JWT.of(token).getPayload("id").toString();
            String roleId = JWT.of(token).getPayload("roleId").toString();
            log.info("id:{},roleId:{}",id,roleId);
            //redis+token -> 该角色拥有的权限列表
            List<String> permissions = redisTemplate.opsForList().range(token, 0, -1);

            //handler->method->注解->访问这个方法需要的权限表达式
            HandlerMethod handlerMethod=(HandlerMethod) handler;
            RequestPermission annotation = handlerMethod.getMethodAnnotation(RequestPermission.class);
            //需要的权限表达式 是否在  角色拥有的权限列表
            for (String permission : permissions) {
                // 在 放行 -> 表达式能对应上
                if(permission.equals(annotation.expression())){
                    return true;
                }
            }

        }
        //封装返回
        try {
            response.setContentType("text/json;charset=utf-8");
            //对象->json
            response.getWriter().write(JSONUtil.toJsonStr(Result.error("权限不足")) );
        } catch (IOException e) {
            throw new RuntimeException(e);
        }

        return false;
    }
}
